package com.yoooya.base.utils;

import org.apache.commons.codec.binary.Hex;

import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.Mac;
import javax.crypto.NoSuchPaddingException;
import javax.crypto.spec.SecretKeySpec;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import java.security.InvalidKeyException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Base64;

public abstract class SecurityUtils {

    private static final String KEY_ALGORITHM = "AES";
    private static final String DEFAULT_CIPHER_ALGORITHM = "AES/ECB/PKCS5Padding";

    public static String md5(String s) throws NoSuchAlgorithmException {
        return md5(s, StandardCharsets.ISO_8859_1);
    }

    public static String md5(String s, Charset charset) throws NoSuchAlgorithmException {
        MessageDigest md = MessageDigest.getInstance("MD5");
        md.update(s.getBytes(charset));
        return Hex.encodeHexString(md.digest());
    }

    public static String sha1(String s) throws NoSuchAlgorithmException {
        return sha1(s, StandardCharsets.ISO_8859_1);
    }

    public static String sha1(String s, Charset charset) throws NoSuchAlgorithmException {
        MessageDigest crypt = MessageDigest.getInstance("SHA-1");
        crypt.reset();
        crypt.update(s.getBytes(charset));
        byte[] digest = crypt.digest();
        return Hex.encodeHexString(digest);
    }

    public static String hmacSha1(String s, String key) throws NoSuchAlgorithmException, InvalidKeyException {
        SecretKeySpec signingKey = new SecretKeySpec(key.getBytes(StandardCharsets.ISO_8859_1), "HmacSHA1");
        Mac mac = Mac.getInstance("HmacSHA1");
        mac.init(signingKey);
        byte[] bs = mac.doFinal(s.getBytes(StandardCharsets.ISO_8859_1));
        return Hex.encodeHexString(bs);
    }

    public static String encode(String s) {
        return Base64.getEncoder().encodeToString(s.getBytes(StandardCharsets.UTF_8));
    }

    public static String decode(String s) {
        return new String(Base64.getDecoder().decode(s), StandardCharsets.UTF_8);
    }

    public static String encrypt(String key, String plaintext) throws NoSuchPaddingException, NoSuchAlgorithmException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException {
        SecretKeySpec sks = new SecretKeySpec(key.getBytes(), KEY_ALGORITHM);
        Cipher cipher = Cipher.getInstance(DEFAULT_CIPHER_ALGORITHM);
        cipher.init(Cipher.ENCRYPT_MODE, sks);

        byte[] bs = plaintext.getBytes();
        bs = cipher.doFinal(bs);
        return org.apache.commons.codec.binary.Base64.encodeBase64String(bs);
    }

    public static String decrypt(String key, String password) throws NoSuchPaddingException, NoSuchAlgorithmException, InvalidKeyException, BadPaddingException, IllegalBlockSizeException {
    	SecretKeySpec sks = new SecretKeySpec(key.getBytes(), KEY_ALGORITHM);
        Cipher cipher = Cipher.getInstance(DEFAULT_CIPHER_ALGORITHM);
        cipher.init(Cipher.DECRYPT_MODE, sks);

        byte[] bs = org.apache.commons.codec.binary.Base64.decodeBase64(password);
        bs = cipher.doFinal(bs);
        return new String(bs);
    }

}
